<template>
  <div>
    <el-dialog id="el-dialog" :visible.sync="dialogFormVisible" title="查看监控视频" fullscreen>
      <el-form :inline="true">
        <el-row>
          <el-col :span="14">
            <el-form-item label="监控角度">
              <el-select v-model="searchForm.channelId" placeholder="请选择监控角度" clearable>
                <el-option v-for="device in deviceList" :key="device.channelId" :label="device.channelName" :value="device.channelId" />
              </el-select>
            </el-form-item>
          </el-col>
          <el-col :span="9.5">
            <el-form-item label="监控时间">
              <el-date-picker
                v-model="searchForm.startTime"
                type="datetime"
                placeholder="开始日期"
                value-format="yyyy-MM-dd HH:mm:ss"
              />
              <span style="margin: 0 5px;">至</span>
              <el-date-picker
                v-model="searchForm.endTime"
                type="datetime"
                placeholder="结束日期"
                value-format="yyyy-MM-dd HH:mm:ss"
              />
            </el-form-item>
          </el-col>
          <el-col :span="1.5">
            <el-button type="primary" size="medium" @click="search">查询</el-button>
          </el-col>
        </el-row>
      </el-form>
      <div id="container" />
      <div>
        <el-button type="primary" size="medium" @click="flvPlay">播放</el-button>
        <el-button type="primary" size="medium" @click="flvPause">暂停</el-button>
      </div>
    </el-dialog>
  </div>
</template>
<script>
import EzuikitFlv from 'ezuikit-flv'
export default {
  name: 'VideoMonitor',
  data() {
    return {
      deviceList: [],
      player: null,
      flvUrl: '',
      flvUrlId: '',
      videoList: [],
      videoIndex: 0,
      dialogFormVisible: false,
      searchForm: {
        channelId: '',
        startTime: '',
        endTime: ''
      }
    }
  },
  mounted() {},
  created() {},
  methods: {
    open() {
      this.dialogFormVisible = true
      if (this.checkHikToken()) {
        this.getHikDeviceChannelList(this.storeNo)
      }
    },
    // 检查海康云平台token是否过期
    checkHikToken() {
      const token = localStorage.getItem('rcpHikToken')
      const expireTime = parseInt(localStorage.getItem('rcpHikTokenExpireTime'))
      if (expireTime === null || token === null || token === '' || Date.now() >= expireTime) {
        if (this.generateHikToken()) {
          return true
        } else {
          return false
        }
      } else {
        return true
      }
    },
    // 生成海康云平台token
    generateHikToken() {
      const axios = require('axios')
      const qs = require('qs')
      const clientId = process.env.VUE_APP_HAIK_CLOUD_APP_KEY
      const clientSecret = process.env.VUE_APP_HAIK_CLOUD_APP_SECRET
      const apiGwBaseUrl = process.env.VUE_APP_API_GW
      const data = qs.stringify({
        'client_id': clientId,
        'client_secret': clientSecret,
        'grant_type': 'client_credentials'
      })
      const config = {
        method: 'post',
        maxBodyLength: Infinity,
        url: apiGwBaseUrl + '/gw/rcp/v1/hik/oauth/token',
        headers: {
          'Content-Type': 'application/x-www-form-urlencoded'
        },
        data: data
      }
      axios.request(config)
        .then((response) => {
          const token = response.data.access_token
          localStorage.setItem('rcpHikToken', 'Bearer ' + token)
          const tokenExpireTime = Date.now() + response.data.expires_in * 1000
          localStorage.setItem('rcpHikTokenExpireTime', tokenExpireTime.toString())
          return true
        })
        .catch((error) => {
          this.$message.error(error)
          return false
        })
    },
    // 根据门店编号获取海康设备通道列表
    getHikDeviceChannelList(storeNo) {
      const axios = require('axios')
      const apiGwBaseUrl = process.env.VUE_APP_API_GW
      const token = localStorage.getItem('rcpHikToken')
      const config = {
        method: 'get',
        maxBodyLength: Infinity,
        url: apiGwBaseUrl + '/gw/rcp/v1/hik/customization/store/cameraList?storeNo=' + storeNo + '&pageNo=1&pageSize=999',
        headers: {
          'Authorization': token
        }
      }
      axios.request(config)
        .then((response) => {
          this.$set(this, 'deviceList', response.data.data.rows)
        })
        .catch((error) => {
          this.$message.error(error)
        })
    },
    // 获取标准流预览地址
    getHikLiveAddress() {
      let deviceSerial
      let channelNo
      for (const deviceListElement of this.deviceList) {
        if (deviceListElement.channelId === this.searchForm.channelId) {
          deviceSerial = deviceListElement.deviceSerial
          channelNo = deviceListElement.channelNo
          break
        }
      }
      if (this.checkHikToken()) {
        const apiGwBaseUrl = process.env.VUE_APP_API_GW
        const token = localStorage.getItem('rcpHikToken')
        const axios = require('axios')
        const data = JSON.stringify({
          'deviceSerial': deviceSerial,
          'channelNo': channelNo,
          'protocol': 4,
          'type': 2,
          'startTime': this.searchForm.startTime,
          'endTime': this.searchForm.endTime
        })

        const config = {
          method: 'post',
          maxBodyLength: Infinity,
          url: apiGwBaseUrl + '/gw/rcp/v1/customization/liveStudio/actions/getLiveAddress',
          headers: {
            'Authorization': token,
            'Content-Type': 'application/json'
          },
          data: data
        }
        axios.request(config)
          .then((response) => {
            if (response.data.code === 200 && response.data.data.url !== null) {
              this.flvUrl = response.data.data.url
              this.flvUrlId = response.data.data.id
              this.flvPlay()
            } else if (response.data.code === 60019) {
              // 设备加密,先关闭设备加密
              this.turnOffHikDeviceEncryption(deviceSerial)
            } else {
              this.$message.error(response.data.message)
            }
          })
          .catch((error) => {
            this.$message.error(error)
          })
      }
    },
    // 关闭设备加密
    turnOffHikDeviceEncryption(deviceSerial) {
      const apiGwBaseUrl = process.env.VUE_APP_API_GW
      const token = localStorage.getItem('rcpHikToken')
      const axios = require('axios')
      const data = JSON.stringify({
        'deviceSerial': deviceSerial
      })
      const config = {
        method: 'post',
        maxBodyLength: Infinity,
        url: apiGwBaseUrl + '/gw/rcp/v1/customization/liveStudio/actions/encryptTurnOffOrOn',
        headers: {
          'Authorization': token,
          'Content-Type': 'application/json'
        },
        data: data
      }
      axios.request(config)
        .then((response) => {
          if (response.data.code === 200) {
            // 设备加密关闭成功
            this.getHikLiveAddress()
          } else {
            this.$message.error('设备加密关闭失败')
          }
        })
        .catch((error) => {
          this.$message.error(error)
        })
    },
    search() {
      if (this.searchForm.channelId === undefined || this.searchForm.channelId === null || this.searchForm.channelId === '' ||
        this.searchForm.startTime === undefined || this.searchForm.startTime === null || this.searchForm.startTime === '' ||
        this.searchForm.endTime === undefined || this.searchForm.endTime === null || this.searchForm.endTime === ''
      ) {
        this.$message.error('请选择监控角度和监控时间')
      } else {
        // 获取标准流预览地址
        this.getHikLiveAddress()
      }
    },
    createPlayer() {
      this.player = new EzuikitFlv({
        container: document.getElementById('container'),
        url: this.flvUrl,
        useMSE: true,
        decoder: 'decoder.js' // 软解解码资源 （wasm 要和js 在同一个文件夹中）
      })
    },
    flvPlay() {
      if (this.player) {
        this.player.destroy()
        this.player = null
      }
      this.createPlayer()
      this.player.play()
    },
    flvPause() {
      this.player.pause()
    }
  }
}
</script>
<style>
#container {
  width: 100%;
  height: 400px;
  background: #000;
}
</style>
